#include <linux/init.h>
#include <linux/module.h>
#include <linux/input.h>
#include <linux/interrupt.h>
#include <linux/of_irq.h>
#include <linux/of.h>

#include <asm/io.h>



#define GPXCON_REG 0x11000c20

int irqnum;
void *regbase;

struct input_dev *inputdev;


int get_irqno_from_node(void)
{
	int irqnum;
	//名字为节点
	struct device_node *np = of_find_node_by_path("/key_init_node");
	if(np)
	{
		printk("find node ok\n");
	}
	else
	{
		printk("find node failed\n");
	}

	irqnum=irq_of_parse_and_map(np,0);
	printk("irqnum=%d\n",irqnum);
	return irqnum;
}

irqreturn_t input_key_irq_handler(int irqnum,void *devid)
{
	int value;
	printk("---------key3-------\n");
	
	value = readl(regbase+4)&(1<<2);
	if(value)
	{
		input_event(inputdev, EV_KEY, KEY_POWER, 0);
		input_sync(inputdev);
	}
	else
	{
		input_event(inputdev, EV_KEY, KEY_POWER, 1);
		input_sync(inputdev);
	}
	return IRQ_HANDLED;
}


static int __init input_init(void)
{
	int ret;
	inputdev=input_allocate_device();
	if(inputdev==NULL)
	{
		printk(KERN_ERR "input_allocate_device failed\n");
		return -ENOMEM;
	}

	inputdev->name="input key";
	inputdev->phys="key/input/input0";
	inputdev->uniq="4412 key0";
	inputdev->id.bustype=BUS_HOST;
	inputdev->id.vendor=0x666;
	inputdev->id.product=0x777;
	inputdev->id.version=0x001;


	__set_bit(EV_KEY,inputdev->evbit);
	__set_bit(KEY_POWER,inputdev->keybit);

	ret=input_register_device(inputdev);
	if(ret!=0)
	{
		printk(KERN_ERR "input_register_device failed\n");
		goto err_0;
	}

	irqnum=get_irqno_from_node();
	ret = request_irq(irqnum,input_key_irq_handler,IRQF_TRIGGER_FALLING|IRQF_TRIGGER_RISING,"key3",NULL);
	if(ret != 0)
	{
		printk("request_irq failed\n");
		goto err_1;
	}

	regbase=ioremap(GPXCON_REG, 8);
	
	return 0;


err_1:
input_unregister_device(inputdev);
err_0:
	input_free_device(inputdev);
	return ret;
}

static void __exit input_exit(void)
{
	iounmap(regbase);
	free_irq(irqnum, NULL);
	input_unregister_device(inputdev);
	input_free_device(inputdev);
}




module_init(input_init);
module_exit(input_exit);
MODULE_LICENSE("GPL");

